/**
 * @file EdgeDetection.h
 * @author enemy1205 (enemy1205@qq.com)
 * @brief Canny边缘检测算法头文件
 * @note 包含Sobel,Canny两类api的实现
 * @date 2021-09-27
 */
#pragma once

#include <opencv2/core/core.hpp>
#include <opencv2/imgcodecs/imgcodecs.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <string>
#include <opencv2/imgproc.hpp>

using namespace cv;

//TODO 需完善类对象私有化，提供对外接口
class _Sobel {
public:
    _Sobel(Mat &, int);

    Mat edgeMag;//边缘梯度图
    bool L2graydient;//是否精确计算幅值
    Mat dst_X, dst_Y;//X,Y方向梯度图
    //计算平滑算子
    Mat calSmoothOperator(int k_size);

    //计算差分算子
    Mat calDifferOperator(int k_size);

    //二维图像卷积
    void conv2D(Mat &, Mat &, Mat &, int ddepth);

    //先垂直方向卷积，后水平方向卷积
    void sepConv2D_Y_X(Mat &, Mat &, Mat &, Mat &, int ddepth);

    //先水平方向卷积，后垂直方向卷积
    void sepConv2D_X_Y(Mat &, Mat &, Mat &, Mat &, int ddepth);

};

class EdgeDetection {
public:
    //构造函数
    EdgeDetection(const std::string &, int kernel_size);

    //非极大值抑制
    void NonMaximumSuppression(const _Sobel &, Mat &) const;

    //双阈值处理
    void DualThresholdProcessing(const Mat &);

    //canny边缘检测主程序
    void Edge_Canny();

    Mat src;//源图
//    Mat padded_img;
    Mat edge_dst;
    int k_size;//算子长度
    uchar TL;//低阈值
    uchar TH;//高阈值
//    void padding();//边缘扩充

};

